﻿using System;

namespace KinonekoSoftware.Studio.Components
{
    public partial class CharacterPickerViewModel : SelectionDialog<Character>
    {
        internal const string Key_Instance = "data";
        internal const string Key_IsSingle = "mode";


        private static TalkingEngine _Engine;


        //-------------------------------------------------------------
        //
        //          Contracts
        //
        //-------------------------------------------------------------

        public static Task<Result<IList<Character>>> Multiple()
        {
            //
            //
            _Engine ??= Platform.GetEngine<TalkingEngine>();


            var instances = _Engine.GetCharacters().ToList();
            var context   = new DialogContext();

            //
            //
            context.Set(ContextBase.Key_Value, instances);
            context.Set(Key_IsSingle, false);

            //
            //
            return Dialog<IList<Character>>(new CharacterPickerViewModel(), context);
        }

        public static Task<Result<IList<Character>>> Multiple(ISet<string> idPool)
        {
            //
            //
            _Engine ??= Platform.GetEngine<TalkingEngine>();
            var instances = _Engine.GetCharacters(idPool).ToList();
            var context   = new DialogContext();

            //
            //
            context.Set(ContextBase.Key_Value, instances);
            context.Set(Key_IsSingle, false);

            //
            //
            return Dialog<IList<Character>>(new CharacterPickerViewModel(), context);
        }


        public static async Task<Result<Character>> SingleOf()
        {
            //
            //
            _Engine ??= Platform.GetEngine<TalkingEngine>();

            var instances = _Engine.GetCharacters().ToList();
            var context   = new DialogContext();

            //
            //
            context.Set(ContextBase.Key_Value, instances);
            context.Set(Key_IsSingle, true);

            //
            //
            var r = await Dialog<IList<Character>>(new CharacterPickerViewModel(), context);

            if (!r.IsFinished)
            {
                return Result<Character>.Failed(CodariaSR.Text_Parameter_EmptyName);
            }

            if (r.Value?.Count == 0)
            {
                return Result<Character>.Failed(CodariaSR.Text_Parameter_EmptyName);
            }

            return Result<Character>.Success(r.Value
                                              .FirstOrDefault());
        }

        public static async Task<Result<Character>> SingleOf(ISet<string> excludeIdSet)
        {
            //
            //
            _Engine ??= Platform.GetEngine<TalkingEngine>();

            //
            //
            excludeIdSet ??= new HashSet<string>();

            var instances = _Engine.GetCharacters(excludeIdSet).ToList();
            var context   = new DialogContext();

            //
            //
            context.Set(ContextBase.Key_Value, instances);
            context.Set(Key_IsSingle, true);

            //
            //
            var r = await Dialog<IList<Character>>(new CharacterPickerViewModel(), context);

            if (!r.IsFinished)
            {
                return Result<Character>.Failed(CodariaSR.Text_Parameter_EmptyName);
            }

            if (r.Value?.Count == 0)
            {
                return Result<Character>.Failed(CodariaSR.Text_Parameter_EmptyName);
            }

            return Result<Character>.Success(r.Value
                                              .FirstOrDefault());
        }


        //-------------------------------------------------------------
        //
        //          Command Handlers
        //
        //-------------------------------------------------------------

        public CharacterPickerViewModel()
        {
            Instances = new ObservableCollection<Character>();
        }



        //-------------------------------------------------------------
        //
        //          Command Handlers
        //
        //-------------------------------------------------------------

        protected override void CreateValidationRules(ICollection<DialogRule> rules)
        {
        }

        protected sealed override bool OnReceive(DialogContext context)
        {

            var single    = context.GetBoolean(Key_IsSingle);
            var instances = context.GetObject<List<Character>>(ContextBase.Key_Value);

            IsMultipleSelection = !single;
            Instances.AddMany(instances, true);
            return false;
        }
        public ObservableCollection<Character> Instances           { get; }
    }
}